﻿using System;
using System.Linq;
using System.Text;
using System.IO;
using System.Data;
using CodeCrawler.UI.Data;

namespace OWASP.CodeReview.CodeCrawler.Engine.CrawlerServerScan {

    /// <summary>
    /// Code Crawler Server Engine Database Core.
    /// This code will grab a list of files located into a remote machine.
    /// 
    /// Assumptions: User privileges are granted
    /// </summary>
    internal class Core {

        /// <summary>
        /// File being processed
        /// </summary>
        private string currentFileName = string.Empty;

        /// <summary>
        /// Remote Folder Path
        /// </summary>
        private string _remoteFolderPath = string.Empty;

        /// <summary>
        /// Remote Folder Path
        /// </summary>
        public string RemoteFolderPath {
            get {
                return _remoteFolderPath;
            }
            set {
                if (value.Trim().Length > 0) { _remoteFolderPath = value; }
            }
        }


        /// <summary>
        /// Create Remote Folder Path
        /// </summary>
        /// <param name="ipAddress"></param>
        /// <param name="remoteFolder"></param>
        /// <returns></returns>
        internal string GetRemoteFolderCombined(string ipAddress, string remoteFolder) {
            
            #region Remote Disk Drive Network String Replacement
            remoteFolder = remoteFolder.ToLower().Replace(@"a:\", @"a$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"b:\", @"b$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"c:\", @"c$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"d:\", @"d$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"e:\", @"e$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"f:\", @"f$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"g:\", @"g$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"h:\", @"h$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"i:\", @"i$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"l:\", @"l$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"m:\", @"m$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"n:\", @"n$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"o:\", @"o$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"p:\", @"p$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"q:\", @"q$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"r:\", @"r$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"s:\", @"s$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"t:\", @"t$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"u:\", @"u$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"v:\", @"v$\");
            remoteFolder = remoteFolder.ToLower().Replace(@"z:\", @"z$\");
            #endregion

            return string.Concat(@"\\",ipAddress, @"\",remoteFolder);
        }
        
        /// <summary>
        /// Grabs a list of all the files located in a remote location.
        /// Process results using Code Crawler Engine.
        /// 
        /// For each result set, a new DataTable will be created into the main dataSet Object which is the output of the Core.
        /// </summary>
        /// <param name="ipAddress"></param>
        /// <param name="remoteFolder"></param>
        /// <param name="extension"></param>
        /// TODO: Improve me
        internal DataSet Scan(string ipAddress, string remoteFolder, string extension) {

            RemoteFolderPath = GetRemoteFolderCombined(ipAddress, remoteFolder);

            string[] _xmlFiles = null;

            try { _xmlFiles = System.IO.Directory.GetFiles(RemoteFolderPath, extension); } 
                catch (DirectoryNotFoundException) {
                    System.Windows.Forms.MessageBox.Show("Directory doesn't exists", "FileIO Exception", System.Windows.Forms.MessageBoxButtons.OK, System.Windows.Forms.MessageBoxIcon.Information);
                    return null;
                }
            
            CodeCrawlerXMLDatabase databasehelper = new CodeCrawlerXMLDatabase();

            DataSet _results = new DataSet();

            foreach (string __singleFile in _xmlFiles) {
                currentFileName = __singleFile.Replace(RemoteFolderPath, string.Empty);

                // Removing this will end up with a [[Child list for field {ItemName without dot and extension}]]
                currentFileName = currentFileName.Replace(".", "#");

                DataTable _currentThreatListDataTable   = new DataTable("ThreatList");
                databasehelper.CreateThreatTable(_currentThreatListDataTable);

                #region OLD CODE
                //if (File.Exists(__singleFile)) {

                //    StreamReader re     = File.OpenText(__singleFile);
                //    string _input       = null;
                //    int _lineNumber     = 1;
                //    int _warnings       = 0;

                //    OWASP.CodeReview.CodeCrawler.Engine.KeyPointersScan.ThreatCollection _threatCollectionList
                //                        = new OWASP.CodeReview.CodeCrawler.Engine.KeyPointersScan.ThreatCollection();

                //    OWASP.CodeReview.CodeCrawler.DataBase.CodeCrawlerXMLDatabase DatabaseObjects
                //                        = new OWASP.CodeReview.CodeCrawler.DataBase.CodeCrawlerXMLDatabase();

                //    CodeCrawlerXMLDatabase dbObject         = new CodeCrawlerXMLDatabase();
                //    DataSet xmlCodeCrawlerDatabase  = dbObject.InizializeCodeCrawlerDatabase();

                //    // This will do the nasty job
                //    while ((_input = re.ReadLine()) != null) {

                //        Engine.Threat _threatObject = _threatCollectionList.ParseLineOfCode(_input, xmlCodeCrawlerDatabase, _lineNumber);
                        
                //        if (_threatObject != null) {

                //            _warnings++;
                //            Engine.KeyPointersScan.ThreatCollection _collection =
                //                                                new OWASP.CodeReview.CodeCrawler.Engine.KeyPointersScan.ThreatCollection();

                //            _collection.AddThreatItem(_threatObject, _currentThreatListDataTable);
                //            _currentThreatListDataTable.TableName = __singleFile;}

                //        _lineNumber++;}

                //    _currentThreatListDataTable.TableName = currentFileName;
                //    _results.Tables.Add(_currentThreatListDataTable);}

                //_currentThreatListDataTable = null;
                #endregion
            } // FINISHED LOOPING THROUGH COLLECTION

            // Return the Results
            return _results;
        }}
        }